using System;
using System.Collections.Generic;
using Castle.MicroKernel;
using Castle.MicroKernel.Handlers;
using Castle.MicroKernel.Registration;
using SpecMaker.Core.Interfaces;
using System.Linq;
namespace SpecMaker.Core
{
    public class SpecFinder : ISpecFinder
    {
        public ISpecContainer[] GetImpl(Type[] types)
        {
            IKernel kernel = new DefaultKernel();
            var containers = new List<ISpecContainer>(); 
            foreach (var type in types)
            {
               
                if(typeof(ISpecContainer).IsAssignableFrom(type))
                {
                    kernel.Register(Component.For(type));
                    try
                    {
                        containers.Add(kernel.Resolve(type.FullName, type) as ISpecContainer);
                    }
                    catch(HandlerException ex)
                    {
                        recurseregister( kernel, type, containers);
                        
                    }
                }
            }
            return containers.ToArray();
        }
        private void recurseregister(IKernel kernel, Type typeresolving, List<ISpecContainer> containers)
        {
            var ctor = typeresolving.GetConstructors().OrderBy(x=>x.GetParameters().Length).First();//get least args constructor
            var ctorparams = ctor.GetParameters();
            foreach (var info in ctorparams)
            {
                if(kernel.HasComponent(info.ParameterType))
                {
                    
                }
                else
                {
                    try
                    {
                        kernel.Register(Component.For(info.ParameterType));
                    }catch
                    {
                        //FIXME: get rid of me this is sooooo bad it hurts
                    }

                }

            } 
            try
            {
                containers.Add(kernel.Resolve(typeresolving.FullName, typeresolving) as ISpecContainer);
            }
            catch(HandlerException)
            {
                recurseregister(kernel, typeresolving, containers);
            }
        }
    }
}